/*
 * Lenovo Group
 * Copyright (c) 2015-2016 All Rights Reserved.
 * 
 * Project Name:event-recoder
 * Create Time: 2016年3月4日 上午8:38:26
 */
package com.lenovo.lmrp.server.eventrecorder.repository;

import java.util.Date;
import java.util.LinkedList;
import java.util.List;

import javax.inject.Inject;

import com.datastax.driver.core.BatchStatement;
import com.datastax.driver.core.ResultSet;
import com.lenovo.lmrp.api.model.entity.EngineerTracePO;
import com.lenovo.lmrp.api.model.entity.ExceptionEventPO;
import com.lenovo.lmrp.api.model.entity.TicketEventPO;
import com.lenovo.lmrp.server.eventrecorder.domain.ticket.IEventRepository;
import com.lenovo.sdc.framework.util.JSONHelper;
import com.lenovo.sdc.framework.util.exception.ErrorCode;
import com.lenovo.sdc.framework.util.exception.TraceableException;

/**
 * 
 * @author wujin
 * @version v1.0
 */
public class EventRepository implements IEventRepository {
    private static final String SQL_INSERT_TICKET_EVENT = "insert into lmrp.ticket_event"
                                                        + "(itsmcode,ticketid,tsreal,source,action,content) "
                                                        + "values(?,?,?,?,?,?);";
    
    private static final String SQL_INSERT_ENGINEER_TRACE = "insert into lmrp.engineer_trace"
                                                        + "(itsmcode,engineerid,tsreal,action,address,longitude,latitude,content) "
                                                        + "values(?,?,?,?,?,?,?,?);";
    
    private static final String SQL_INSERT_EXCEPTION_EVENT = "insert into lmrp.exception_event"
                                                        + "(itsmcode,source,tsreal,ecode,error) "
                                                        + "values(?,?,?,?,?);";
    
    private static final String SQL_QUERY_TICKET_EVENT = "select * from lmrp.ticket_event where itsmcode = ? and ticketid = ? order by tsreal;";
    
    private CassandraDataSource dataSource;
    
    @Inject
    public EventRepository(CassandraDataSource dataSource) {
        this.dataSource = dataSource;
    }
    
    @Override
    public void storeTicketEvent(List<TicketEventPO> poList) {
        BatchStatement batchStatement = new BatchStatement();
        for(TicketEventPO po : poList) {
            try {
                dataSource.addBatch(batchStatement, 
                    SQL_INSERT_TICKET_EVENT, 
                    po.getItsmCode(),
                    po.getTicketID(),
                    (po.getEventTime() == null ? new Date() : po.getEventTime()),
                    po.getSource(),
                    po.getAction(),
                    JSONHelper.toJSON(po.getContent()));
            }
            catch (Exception exp) {
                TraceableException.writeLog(ErrorCode.COMM_PARSE_FAILED, "convert content to json", exp);
                continue;
            }
        }
        dataSource.batchExecute(batchStatement);
    }

    @Override
    public List<TicketEventPO> getTicketEvents(String itsmCode, String ticketID) {
        ResultSet result = dataSource.execute(SQL_QUERY_TICKET_EVENT, itsmCode, ticketID);
        List<TicketEventPO> poList = new LinkedList<>();
        result.forEach(action -> {
            TicketEventPO po = new TicketEventPO();
            po.setItsmCode(action.getString("itsmcode"));
            po.setTicketID(action.getString("ticketid"));
            po.setSource(action.getString("source"));
            po.setAction(action.getString("action"));
            po.setContent(action.getString("content"));
            po.setEventTime(action.getTimestamp("tsreal"));
            
            poList.add(po);});
        
        return poList;
    }
    
    @Override
    public void storeEngineerTrace(List<EngineerTracePO> poList) {
        BatchStatement batchStatement = new BatchStatement();
        for (EngineerTracePO po : poList) {
            try {
                dataSource.addBatch(batchStatement, 
                    SQL_INSERT_ENGINEER_TRACE, 
                    po.getItsmCode(),
                    po.getEngineerId(),
                    (po.getTraceTime() == null ? new Date() : po.getTraceTime()),
                    po.getAction(),
                    po.getAddress(),
                    po.getLongitude(),
                    po.getLatitude(),
                    JSONHelper.toJSON(po.getContent()));
            }
            catch (Exception exp) {
                TraceableException.writeLog(ErrorCode.COMM_PARSE_FAILED, "convert content to json when store engineer trace", exp);
                continue;
            }
        }
        dataSource.batchExecute(batchStatement);
    }
    
    @Override
    public void storeExceptionEvent(List<ExceptionEventPO> poList) {
        BatchStatement batchStatement = new BatchStatement();
        for (ExceptionEventPO po : poList) {
            try {
                dataSource.addBatch(batchStatement, 
                    SQL_INSERT_EXCEPTION_EVENT, 
                    po.getItsmCode(),
                    po.getSource(),
                    (po.getEventTime() == null ? new Date() : po.getEventTime()),
                    po.getEcode(),
                    JSONHelper.toJSON(po.getError()));
            }
            catch (Exception exp) {
                TraceableException.writeLog(ErrorCode.COMM_PARSE_FAILED, "convert content to json when store exception event", exp);
                continue;
            }
        }
        dataSource.batchExecute(batchStatement);
    }
}
